home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Linux Cubed Series 7: Sunsite
/
Linux Cubed Series 7 - Sunsite Vol 1.iso
/
system
/
filesyst
/
dosfs
/
dmsdosfs.000
/
dmsdosfs
/
dmsdosfs-0.6.9b
/
dutil.c
< prev
next >
Wrap
C/C++ Source or Header
|
1996-06-23
|
9KB
|
274 lines
/*
dutil.c
DMSDOS filesystem: external utility
The DMSDOS filesystem was written by Frank Gockel
(gockel@etecs4.uni-duisburg.de).
COPYRIGHT (C) 1995,1996 Frank Gockel
Distributed under the GNU General Public License.
*/
#include<stdio.h>
#include<linux/dmsdos_fs.h>
#include<sys/ioctl.h>
#include<sys/types.h>
#include<sys/stat.h>
#include<fcntl.h>
#include<string.h>
#include<errno.h>
#include<unistd.h>
int scan(char*arg)
{ int w;
if(strncmp(arg,"0x",2)==0)sscanf(arg+2,"%x",&w);
else sscanf(arg,"%d",&w);
return w;
}
void error(int err)
{ if(err==-EPERM)printf("Permission denied.\n");
else if(err==-EIO)printf("I/O Error.\n");
else if(err==-EINVAL)printf("Invalid parameter.\n");
else printf("Error %d occured.\n",err);
}
void main(int argc, char*argv[])
{ Dblsb dblsb;
int fd;
int ret;
unsigned long w[10];
double ratio;
struct
{ unsigned long w;
unsigned char data[512];
} buffer;
int i;
char a[100];
char b[100];
char c[100];
Mdfat_entry mde;
if(argc<2)
{
printf("DMSDOS filesystem utility (C) 1995 Frank Gockel\n");
printf("Usage: %s (directory)\n",argv[0]);
printf(" %s (directory) cluster (clusterno)\n",argv[0]);
printf(" %s (directory) sector (sectorno)\n",argv[0]);
printf(" %s (directory) bitfat (sectorno)\n",argv[0]);
printf(" %s (directory) setcomp (comp option)\n",argv[0]);
printf(" %s (directory) setcf (cf option)\n",argv[0]);
printf(" %s (directory) dumpcache\n",argv[0]);
printf(" %s (directory) checkfs\n",argv[0]);
printf(" %s (directory) setmaxcluster (value)\n",argv[0]);
return;
}
fd=open(argv[1],O_RDONLY);
if(fd<0)
{ printf("No such file or directory.\n");
return;
}
/* this hack enables reverse version check */
dblsb.s_dcluster=DMSDOS_VERSION;
ret=ioctl(fd,DMSDOS_GET_DBLSB,&dblsb);
if(ret<0)
{ printf("This is not a DMSDOS directory.\n");
close(fd);
return;
}
printf("You are running DMSDOS Version %d.%d.%d.\n\n",(ret&0xff0000)>>16,
(ret&0x00ff00)>>8,ret&0xff);
if(ret&0x0f000000)
{ printf("Sorry, this utility is too old for the actual dmsdos version.\n");
close(fd);
return;
}
if(ret<0x00000608)
{ printf("This utility requires at least DMSDOS Version 0.6.8.\n");
close(fd);
return;
}
printf("Parameters of the CVF the directory specified belongs to:\n");
printf("dcluster: %5d ",dblsb.s_dcluster);
printf("mdfatstart: %5d ",dblsb.s_mdfatstart);
printf("fatstart: %5d ",dblsb.s_fatstart);
printf("rootdir: %5d\n",dblsb.s_rootdir);
printf("root_entries:%5d ",dblsb.s_rootdiranzentry);
printf("sectperclust:%5d ",dblsb.s_sectperclust);
printf("bootblock: %5d ",dblsb.s_bootblock);
printf("16bitfat: %5s\n",dblsb.s_16bitfat?"yes":"no");
printf("datastart: %7d ",dblsb.s_datastart);
printf("dataend: %7d ",dblsb.s_dataend);
printf("comp: 0x%08x ",dblsb.s_comp);
printf("cfaktor: %7d\n",dblsb.s_cfaktor+1);
printf("max_cluster: %5d ",dblsb.s_max_cluster);
printf("max_cluster2:%5d ",dblsb.s_max_cluster2);
printf("support_lfn: %5d\n",dblsb.s_support_lfn);
if(argc==3)
{
if(strcmp(argv[2],"dumpcache")==0)
{ ioctl(fd,DMSDOS_DUMPCACHE,w);
printf("Caches dumped to syslog.\n");
close(fd);
return;
}
if(strcmp(argv[2],"checkfs")==0)
{ printf("Please wait while filesystem is checked...\n");
ioctl(fd,DMSDOS_SIMPLE_CHECK,w);
if(w[0]==1||w[0]==2)printf("Check aborted due to lack of kernel memory.\n");
if(w[0]==0)printf("No filesystem error found.\n");
if(w[0]==-1)printf("Filesystem has serious errors: FAT level crosslink(s) found.\n");
if(w[0]==-2)printf("Filesystem has serious errors: MDFAT level crosslink(s) found.\n");
if(w[0]==-3)printf("Filesystem has minor errors: BITFAT mismatches MDFAT.\n");
if(w[0]==-1||w[0]==-2)
{ ioctl(fd,DMSDOS_SET_COMP,READ_ONLY);
printf("The filesystem has been set to read-only mode.\n");
}
close(fd);
return;
}
}
if(argc<4)
{
printf("\nPlease wait while filesystem is scanned...\n\n");
ioctl(fd,DMSDOS_EXTRA_STATFS,w);
printf("free sectors: %7ld ",w[0]);
printf("used sectors: %7ld ",w[1]);
printf("all sectors: %7ld\n",w[0]+w[1]);
printf("max free hole: %7ld ",w[2]);
i=(100*(w[0]-w[2]))/w[0];
printf("fragmentation:%7d%% ",i);
i=(100*w[1])/(w[0]+w[1]);
printf("capacity: %7d%%\n",i);
printf("free clusters: %7ld ",w[3]);
printf("used clusters: %7ld ",w[4]);
printf("all clusters: %7ld\n",w[3]+w[4]+w[5]);
printf("compressed: %7ld ",w[8]);
printf("uncompressed: %7ld ",w[9]);
printf("lost clusters: %7ld\n",w[5]);
printf("cluster compression: %5ld%% ",(w[8]+w[9]==0)?0:(100*w[8])/(w[8]+w[9]));
if(w[6]!=0)ratio=((double)w[7])/((double)w[6]);else ratio=2.0;
printf("compression ratio: %5.2f : 1\n",ratio);
printf("compressed space allocated (real allocated space): %7ldKB\n",w[6]/2);
printf("uncompressed space allocated: %7ldKB\n",w[7]/2);
printf("compressed free space (estimated free space): %7dKB\n",
((int)(w[0]*ratio))/2);
printf("uncompressed free space: %7ldKB\n",w[0]/2);
printf("maximum free space due to cluster limit: %7ldKB\n",
w[3]*dblsb.s_sectperclust/2);
if(w[2]<=dblsb.s_sectperclust*3&&w[0]>dblsb.s_sectperclust*3)
printf("Warning: This CVF should immediately be defragmented at internal MDFAT level.\n"
" Do not write to this CVF unless you have defragmented it.\n");
else
if(w[0]<=dblsb.s_sectperclust*3)
printf("Warning: This CVF is full. Do not write to it.\n");
else
if(dblsb.s_full)
printf("Warning: This CVF is full or too fragmented at internal MDFAT\n"
" level, non-root write access is refused.\n");
else
if(w[3]*dblsb.s_sectperclust<w[0])
{
printf("Warning: You cannot use all free space of this CVF due to the cluster limit.\n");
i=((int)(w[0]*ratio))/dblsb.s_sectperclust-w[3]+dblsb.s_max_cluster;
if(i>dblsb.s_max_cluster2)i=dblsb.s_max_cluster2;
if(i>dblsb.s_max_cluster)
printf(" Enlarge the max_cluster value or the dos compression ratio.\n"
" I recommend the following max_cluster value for this CVF: %d\n",i);
}
}
else if(strcmp(argv[2],"bitfat")==0)
{ w[0]=scan(argv[3]);
ret=ioctl(fd,DMSDOS_READ_BITFAT,w);
if(ret<0)error(ret);
else
{ if(w[1]==0)printf("\nbitfat: sector is free\n");
if(((signed long)w[1])>0)printf("\nbitfat: sector is allocated\n");
if(((signed long)w[1])<0)printf("\nbitfat: value out of range\n");
}
}
else if(strcmp(argv[2],"cluster")==0)
{ w[0]=scan(argv[3]);
w[1]=&mde;
ret=ioctl(fd,DMSDOS_READ_MDFAT,w);
if(ret<0)error(ret);
else
{
printf("used: %s\n",(mde.flags&2)?"yes":"no");
if(w[1]&0x80000000)
printf("compressed: %s\n",(mde.flags&1)?"no":"yes");
printf("size uncompressed: %d compressed: %d\n",
mde.size_hi_minus_1+1,mde.size_lo_minus_1+1);
printf("first sector: %ld\n",mde.sector_minus_1+1);
printf("unknown bits: %d\n",mde.unknown);
ret=ioctl(fd,DMSDOS_READ_DFAT,w);
if(ret<0)error(ret);
else printf("next cluster: %ld\n",w[1]);
}
}
else if(strcmp(argv[2],"sector")==0)
{ buffer.w=scan(argv[3]);
ret=ioctl(fd,DMSDOS_READ_BLOCK,&buffer);
if(ret<0)error(ret);
else
{
for(i=0;i<512;++i)
{ if(i%16==0){sprintf(a,"%3X : ",i);strcpy(b,"");}
sprintf(c," %02X",buffer.data[i]);
strcat(a,c);
if(buffer.data[i]>=32&&buffer.data[i]<128)
sprintf(c,"%c",buffer.data[i]);
else strcpy(c,".");
strcat(b,c);
if(i%16==15)printf("%s %s\n",a,b);
}
}
}
else if(strcmp(argv[2],"setcomp")==0)
{ if(strcmp(argv[3],"ro")==0)ioctl(fd,DMSDOS_SET_COMP,READ_ONLY);
else if(strcmp(argv[3],"no")==0)ioctl(fd,DMSDOS_SET_COMP,UNCOMPRESSED);
else if(strcmp(argv[3],"guess")==0)ioctl(fd,DMSDOS_SET_COMP,GUESS);
else if(strcmp(argv[3],"ds00")==0)ioctl(fd,DMSDOS_SET_COMP,DS_0_0);
else if(strcmp(argv[3],"ds01")==0)ioctl(fd,DMSDOS_SET_COMP,DS_0_1);
else if(strcmp(argv[3],"ds02")==0)ioctl(fd,DMSDOS_SET_COMP,DS_0_2);
else if(strcmp(argv[3],"jm00")==0)ioctl(fd,DMSDOS_SET_COMP,JM_0_0);
else if(strcmp(argv[3],"jm01")==0)ioctl(fd,DMSDOS_SET_COMP,JM_0_1);
else if(strcmp(argv[3],"sq00")==0)ioctl(fd,DMSDOS_SET_COMP,SQ_0_0);
else printf("??? mode %s not recognized.\n",argv[3]);
}
else if(strcmp(argv[2],"setcf")==0)
{ ioctl(fd,DMSDOS_SET_CF,scan(argv[3])-1);
}
else if(strcmp(argv[2],"setmaxcluster")==0)
{ ioctl(fd,DMSDOS_SET_MAXCLUSTER,scan(argv[3]));
}
else printf("??? syntax error in command line.\n");
close(fd);
}